/**
 * File:   tx.h
 * Author:
 *
 */

#ifndef TX_H
#define	TX_H

#include <cstdlib>
#include <pthread.h>
#include <iostream>
#include <vector>
#include "contest_interface.h"
#include "ShadowSpace.h"

using namespace std;

/**
 * Operation    (pointer, object)   RollBack             type   Done Dirty(for rollback)
 * Read           Null, Null      Nothing                 00:0   T/F  T/F
 * Delete         Null, Record    Insert(Record)          01:1   T/F  T/F
 * Insert         Pointer,Null    Delete(Record)          10:2   T/F  T/F
 * Update         Pointer,Record  Update(oldValue)        11:3   T/F  T/F
 */
typedef struct operation { // Not sure
    uint8_t type;
    Iterator *ptr;
    Record r;
    bool done_flag;
    bool dirty_flag;
    uint8_t dup_flag;
    uint8_t count_success_op;
    
    operation();
    operation(uint8_t type_, Iterator *ptr_, Record r_, bool done_);
    operation(uint8_t type_, Iterator *ptr_, Record r_, bool done_, uint8_t dup_);
    ~operation();
} operation;

typedef struct Transaction { //TODO: solve transaction ID problem
private:
    bool auto_commit;
    bool handled;
    uint8_t status; //1:A: aborted, 2:R: running, 3:C: committed
    bool rejected;
    vector<operation*> *operations; //list of operations done by the transaction
    Index *ix;
    ShadowSpace* shadowSpace;
    
public:
    ~Transaction();
    Transaction();
    operation * Tx_pop_opt();

    bool isReject() {
        return this->rejected;
    };
    bool insertOpt(operation * op);

    vector< operation*>* Tx_operations() {
        return this->operations;
    };

    uint8_t Tx_status() {
        return this->status;
    };

    Index * Tx_index() {
        return this->ix;
    };

    bool Tx_is_autoCommit() {
        return this->auto_commit;
    };

    bool Tx_isHandled() {
        return this->handled;
    };

    void Tx_set_asHandeled() {
        this->handled = true;
    };

    void Tx_set_asUnHandeled() {
        this->handled = false;
    };

    void Tx_set_autoCommit() {
        this->auto_commit = true;
    };

    void Tx_opt_init() {
        this->operations = new vector< operation*>;
    };

    void Tx_set_status(uint8_t status_) {
        this->status = status_;
    };

    void Tx_set_index(Index * ix_) {
        this->ix = ix_;
    };
    operation * Tx_find_Record(Record * rec_);

    void Tx_set_Reject() {
        this->rejected = true;
    };

    ShadowSpace * Tx_get_ShadowSpace() {
        return this->shadowSpace;
    };
} Transaction;

#endif	/* TX_H */
